package server;

import java.io.BufferedInputStream;
import java.io.ByteArrayOutputStream;
import java.io.FileInputStream;
import java.io.IOException;

public class ClassLoaderMini extends ClassLoader {

    public static void main(String[] args) throws Exception {

        ClassLoaderMini loader = new ClassLoaderMini(
                "F:/IdeaProjects/Minicat/webapps/demo1/server/LagouServlet.class");
        Class<?> clazz = loader.loadClass("server.LagouServlet");
        HttpServlet o = (HttpServlet) clazz.newInstance();
        System.out.println(o.getClass().getClassLoader());

    }

    private byte[] data;

    public ClassLoaderMini(String clazzPath) throws IOException {
        data = loadClassFile(clazzPath);
    }

    /**
     * 加载class文件
     *
     * @param clazzPath
     *            class绝对文件路径
     * @return 字节数组
     * @throws IOException
     */
    private byte[] loadClassFile(String clazzPath) throws IOException {
        FileInputStream fis = new FileInputStream(clazzPath);
        BufferedInputStream bis = new BufferedInputStream(fis);
        ByteArrayOutputStream baos = new ByteArrayOutputStream();

        byte[] buffer = new byte[1024 * 256];
        int ch = 0;
        while ((ch = bis.read(buffer, 0, buffer.length)) != -1) {
            baos.write(buffer, 0, ch);
        }
        return baos.toByteArray();
    }

    @Override
    protected Class<?> loadClass(String name, boolean resolve)
            throws ClassNotFoundException {
        Class<?> c = findLoadedClass(name);
        if (c == null) {
            // 如果父加载器不为null，使用父类加载器加载（比如Object，HashMap等核心类）
            if (getParent() != null && (!"server.LagouServlet".equals(name))) {
                try {
                    c = getParent().loadClass(name);
                } catch (Exception e) {
                    // 父类可能没加载，则抛异常
                }

            }
            // 如果父类加载器没有加载，再使用自定义加载器加载
            if (c == null) {
                c = defineClass(name, data, 0, data.length);
            }
        }

        return c;
    }

}
